home *** CD-ROM | disk | FTP | other *** search
/ ETO Development Tools 1 / ETO Development Tools 1.iso / Tools - Objects / C++ / MPW C++ 3.1b1 / Examples / CPlusExamples / Count.cp next >
Text File  |  1989-09-29  |  3KB  |  167 lines

  1. #include <CursorCtl.h>
  2. #include <ErrMgr.h>
  3. #include <FCntl.h>
  4. #include <String.h>
  5. #include <Stream.h>
  6. #include <StdLib.h>
  7.  
  8. #include "StreamCounter.h"
  9.  
  10. const int BUFSIZE = 1024;
  11.  
  12. extern "C" { int tolower(int); }
  13.  
  14. class TCountTool {
  15.  
  16.   public:
  17.     TCountTool();
  18.  
  19.     short Control(int*, char* []);
  20.     
  21.   private:
  22.  
  23.     enum mode { both =0, charsOnly =1, linesOnly =2 };
  24.     
  25.     mode    fState;
  26.     aCount    fTotal;
  27.     long    fPad;
  28.  
  29.     short    Parse(int*, char* []);
  30.     void    Print(aCount, char* =0);
  31. };
  32.     
  33.  
  34. static void
  35. error(char* e)
  36. {
  37.     cerr << "### CountTool Error: " << e << "\n";
  38.     exit(1);
  39. }
  40.  
  41. TCountTool::TCountTool()
  42. {
  43.     fState = both;
  44.     fTotal.lines = fTotal.chars = 0;
  45.     fPad = 5; // 5 = strlen("Total");
  46. }
  47.  
  48. short
  49. TCountTool::Parse(int* c, char* v[])
  50. {
  51.     int fc = 0;
  52.     
  53.     for (int p = 1; p < *c; p++) {
  54.         long    length = strlen(v[p]);
  55.  
  56.         if (*v[p] == '-')
  57.             if (tolower(*(v[p]+1)) == 'c' && length == 2)
  58.                 fState = charsOnly;
  59.             else
  60.                 if (tolower(*(v[p]+1)) == 'l' && length == 2)
  61.                     fState = linesOnly;
  62.                 else {
  63.                     cerr << "### Count - \"" << v[p] << "\" is not an option.\n";
  64.                     cerr << "# Usage - Count [-l] [-c] [files …].\n";
  65.                     return 2;
  66.                 }
  67.         else {
  68.             if (fPad < length) fPad = length;
  69.             v[fc++] = v[p];
  70.         }
  71.     }
  72.     *c = fc;
  73.     return 0;
  74. }
  75.  
  76.  
  77. void
  78. TCountTool::Print(aCount c, char* fn)
  79. {
  80.     long    p = 0;
  81.     
  82.     if (fn != 0) {
  83.         cout << fn;
  84.         p = fPad - strlen(fn);
  85.     } 
  86.     if (fState != charsOnly) {
  87.         cout << form("%*d", p+5, c.lines);
  88.         p = 0;
  89.     }
  90.     if (fState != linesOnly)
  91.         cout << form("%*d", p+7, c.chars);
  92.  
  93.     cout << "\n";
  94.     cout.flush();
  95. }
  96.  
  97.  
  98. short
  99. TCountTool::Control(int* ac, char* av[])
  100. {
  101.     InitCursorCtl(0);
  102.  
  103.     if (Parse(ac, av) != 0)        //  parse error (bad argument)
  104.         return 2;
  105.  
  106.     if (*ac == 0) {                //    no parameters - count stdin
  107.         TStreamCounter theCounter;
  108.  
  109.         SpinCursor(16);
  110.         theCounter.Count();
  111.         aCount    counts = theCounter.GetCount();
  112.         Print(counts);
  113.     } else {                    //    count file parameters
  114.         short dirty = 0;
  115.         short tc = 0;
  116.         fstream *fs = 0;
  117.         char buffer[BUFSIZE *8];
  118.         
  119.         for (int i = 0; i < *ac; i++)  {
  120.             int fd = open(av[i], O_RDONLY);
  121.             
  122.             if (fd != EOF) {
  123.                 if (!(fs = new fstream(fd, buffer, BUFSIZE *8))) {
  124.                     error("No Free store available.");
  125.                     dirty++;
  126.                 } else {
  127.                     TStreamCounter theCounter(fs);
  128.                     SpinCursor(16);
  129.                     theCounter.Count();
  130.                     aCount counts = theCounter.GetCount();
  131.                     if (*ac == 1)
  132.                         Print(counts);
  133.                     else {
  134.                         Print(counts, av[i]);
  135.                         fTotal.chars += counts.chars;
  136.                         fTotal.lines += counts.lines;
  137.                         tc++;
  138.                     }
  139.                     delete fs;
  140.                 }
  141.                 
  142.                 close(fd);
  143.             } else {
  144.                 cerr << "### Count - Unable to open file " << av[i] << ".\n";
  145.                 extern short MacOSErr;
  146.                 char buf[256];
  147.                 cerr << "# "<< GetSysErrText(MacOSErr, buf) << ".\n";
  148.                 dirty++;
  149.             }
  150.         }
  151.         
  152.         if (tc > 1)    Print(fTotal, "Total");
  153.     
  154.         if (dirty) return 2;
  155.     
  156.     }
  157.     return 0;
  158. }
  159.  
  160.  
  161. int
  162. main(int argc, char* argv[])
  163. {
  164.     TCountTool myCounter;
  165.     
  166.     return myCounter.Control(&argc, argv);
  167. }